package br.brpv.silvestrin.vendas.mainactivity;

import android.app.Activity;
import android.app.AlertDialog;
import android.content.DialogInterface;
import android.view.View;
import android.widget.*;
import br.brpv.silvestrin.vendas.R;
import br.brpv.silvestrin.vendas.domain.*;
import br.brpv.silvestrin.vendas.manager.ItemsManager;
import br.brpv.silvestrin.vendas.manager.OrderManager;
import br.brpv.silvestrin.vendas.util.ShowMessage;
import br.brpv.silvestrin.vendas.webservice.ServerDataCacheService;

import java.util.ArrayList;


public class AddItemsScreen implements  AddItemInterface, OrderManager.OrderManagerInterface, ItemsManager.ItemsFromServerListener {
    private int codSelectedCompany;


    public enum Mode {WAIT_NEW_ORDER, MAKE_ORDER}
    //private Mode currentMode;

    Activity activity;
    LinearLayout addItemsView;

    DialogAddItem dialogAddItem;

    private Button newOrderButton;
    private Button endingOrderButton;
    private Button backButton;

    private CheckBox stockCheckBox;
    private SearchView searchItemCfg;
    private SearchView searchItem;

    private ItemAdapter adapterItems = null;
    private ItemCfgAdapter adapterItemsCfg = null;
    private AddedItemAdapter adapterAddedItem = null;

    private Item selectedItem = null;

    private String queryItemsText = "";
    private String queryItemsCfgText = "";

    private ArrayAdapter<PriceTable> adapterPriceTable = null;
    private ArrayList<UnitOfMeasurement> unitOfMeasurementArrayList = new ArrayList<UnitOfMeasurement>();
    private String establishmentName = "";
    private boolean levaLoteParaPedido = false;
    private String codPriceTable = "0";

    private ItemsManager itemsManager;
    private OrderManager orderManager;
    private Order order;


    private AddedItemsListInterface addedItemsListInterface;

    public AddItemsScreen(Activity activity, AddedItemsListInterface addedItemsListInterface) {
        this.activity = activity;

        this.addedItemsListInterface = addedItemsListInterface;

        adapterItemsCfg =
                new ItemCfgAdapter(activity, R.layout.list_view_rows_itens_details, new ArrayList<ItemCfg>());
        adapterAddedItem =
                new AddedItemAdapter(activity, R.layout.list_view_rows_added_item, new ArrayList<AddedItem>());
        adapterPriceTable =
                new ArrayAdapter<PriceTable>(activity, R.layout.simple_spinner_item_custom, new ArrayList<PriceTable>());

        //currentMode = AddItemsScreen.Mode.WAIT_NEW_ORDER;

        orderManager = new OrderManager(activity, this);
        itemsManager = new ItemsManager(activity, this);
    }

    public void initAddItemScreen(){
        initHeader();

        initListItems();
        initListItemsCfg();
        initListItensAdded();

        initOnlyStockCheck();
        initButtons();

        if(dialogAddItem == null) dialogAddItem = new DialogAddItem(activity, this);

        TextView totalStock = (TextView) addItemsView.findViewById(R.id.total_in_stock_value);
        adapterItemsCfg.setViewToShowStockSum(totalStock);
    }

    private void initHeader() {
        Spinner priceTableSpinner = (Spinner)addItemsView.findViewById(R.id.price_table_spinner);
        if(priceTableSpinner != null) {
            priceTableSpinner.setOnItemSelectedListener(new SelectPriceTableListener());
            priceTableSpinner.setAdapter(adapterPriceTable);
        }

        TextView clientNameView = (TextView)addItemsView.findViewById(R.id.order_establishment);
        clientNameView.setText(establishmentName);

        CheckBox levaLoteCheckBox = (CheckBox)addItemsView.findViewById(R.id.leva_lote_pedido);
        levaLoteCheckBox.setChecked(levaLoteParaPedido);
        levaLoteCheckBox.setOnCheckedChangeListener(new LevaLoteClickListener());
    }

    private void initButtons() {
        newOrderButton = (Button)addItemsView.findViewById(R.id.final_consumer_new_order);
        newOrderButton.setOnClickListener(new NewOrderButtonListener());

        endingOrderButton = (Button)addItemsView.findViewById(R.id.final_consumer_finish_order);
        endingOrderButton.setVisibility(View.VISIBLE);
        endingOrderButton.setOnClickListener(new EndingOrderButtonListener());

        backButton = (Button)addItemsView.findViewById(R.id.add_item_back_button);
        backButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                addedItemsListInterface.addItemsScreenBackButtonClick();
            }
        });

    }

    public void setVisible(){
        if(addItemsView!=null) addItemsView.setVisibility(View.VISIBLE);
    }
    
    public void setInvisible(){
        if(addItemsView!=null) addItemsView.setVisibility(View.INVISIBLE);
    }

    public void setAddedItems(ArrayList<AddedItem> addedItems){
        adapterAddedItem.clear();
        if(addedItems == null) adapterAddedItem.addAll(new ArrayList<AddedItem>());
        else adapterAddedItem.addAll(addedItems);
        adapterAddedItem.notifyDataSetChanged();
    }

    public void setUnitsOfMeasurement(ArrayList<UnitOfMeasurement> unitOfMeasurements) {
        unitOfMeasurementArrayList = unitOfMeasurements;
        if(dialogAddItem != null) dialogAddItem.setUnitsOfMeasurement(unitOfMeasurementArrayList);
    }

    private void initListItems(){
        ListView itemsList = (ListView)addItemsView.findViewById(R.id.listItens);
        if(itemsList != null) {
            itemsList.setAdapter(adapterItems);
            itemsList.setOnItemClickListener(new ItemListClickListener());
            itemsList.setDrawSelectorOnTop(true);
        }

        QueryItemListener queryItem = new QueryItemListener();
        searchItem = (SearchView) addItemsView.findViewById(R.id.search_item);
        if(searchItem != null) {
            searchItem.setOnQueryTextListener(queryItem);
            searchItem.setOnCloseListener(queryItem);
            searchItem.setQuery(queryItemsText, false);
        }

    }

    private void initListItemsCfg(){

        TextView itemName = (TextView)addItemsView.findViewById(R.id.item_selected);
        if(itemName != null && selectedItem != null) itemName.setText(selectedItem.getName());

        ListView itemsCfgList = (ListView)addItemsView.findViewById(R.id.list_cfg_items);
        if(itemsCfgList != null){
            itemsCfgList.setAdapter(adapterItemsCfg);
            itemsCfgList.setOnItemClickListener(new ItemCfgClickListener());
        }

        searchItemCfg = (SearchView)  addItemsView.findViewById(R.id.search_detailed_item);
        if(searchItemCfg != null){
            QueryItemCfgListener listener = new QueryItemCfgListener();
            searchItemCfg.setOnQueryTextListener(listener);
            searchItemCfg.setQuery(queryItemsCfgText, true);
            searchItemCfg.setOnCloseListener(listener);
        }
    }

    private void initListItensAdded(){
        ListView addedItemsList = (ListView)addItemsView.findViewById(R.id.addedItems_list);
        if(addedItemsList != null){
            addedItemsList.setAdapter(adapterAddedItem);
            addedItemsList.setOnItemClickListener(new AdapterView.OnItemClickListener() {
                @Override
                public void onItemClick(AdapterView<?> adapterView, View view, int i, long l) {
                    AddedItem addedItem = adapterAddedItem.getItem(i);
                    dialogAddItem.showEditItem(order.getCompanyId(), addedItem);
                }
            });
        }

    }

    private void initOnlyStockCheck(){
        stockCheckBox = (CheckBox)addItemsView.findViewById(R.id.stock_itens);
        stockCheckBox.setChecked(true);
        stockCheckBox.setOnClickListener(new checkBoxStockItemListener());
    }

    private void initItemList(ArrayList<Item> items) {
        clearAddItemsView();

        adapterItems = new ItemAdapter(activity, R.layout.list_view_row_items, items);

        ListView itemsList = (ListView)addItemsView.findViewById(R.id.listItens);
        if(itemsList != null) {
            itemsList.setAdapter(adapterItems);
            adapterItems.notifyDataSetChanged();
        }

        setAddItemsMode(AddItemsScreen.Mode.MAKE_ORDER);
        addedItemsListInterface.initializeAddingItems();
    }

    private void clearAddItemsView(){
        levaLoteParaPedido = false;

        if(adapterPriceTable != null){
            adapterPriceTable.clear();
        }

        if(adapterItemsCfg != null) {
            adapterItemsCfg.clear();
            adapterItemsCfg.notifyDataSetChanged();
        }
        if(adapterAddedItem != null){
            adapterAddedItem.clear();
            adapterAddedItem.notifyDataSetChanged();
        }
        if(adapterItems != null){
            adapterItems.clear();
            adapterItems.notifyDataSetChanged();
        }

        if(addItemsView != null) {
            TextView itemName = (TextView) addItemsView.findViewById(R.id.item_selected);
            if(itemName != null) itemName.setText("");
            SearchView searchItem = (SearchView) addItemsView.findViewById(R.id.search_item);
            if(searchItem != null) searchItem.setQuery("", false);
            SearchView searchItemCfg = (SearchView)  addItemsView.findViewById(R.id.search_detailed_item);
            if(searchItemCfg != null) searchItemCfg.setQuery("", false);
            CheckBox levaLoteCheckBox = (CheckBox)addItemsView.findViewById(R.id.leva_lote_pedido);
            if(levaLoteCheckBox != null) levaLoteCheckBox.setChecked(levaLoteParaPedido);
        }
        selectedItem = null;
    }

    public void setAddItemsMode(Mode mode){
        switch (mode) {
            case MAKE_ORDER:
                if(endingOrderButton != null) endingOrderButton.setVisibility(View.VISIBLE);
                //currentMode = AddItemsScreen.Mode.MAKE_ORDER;

                break;
            case WAIT_NEW_ORDER:
                clearAddItemsView();
                //currentMode = AddItemsScreen.Mode.WAIT_NEW_ORDER;
                if(endingOrderButton != null) endingOrderButton.setVisibility(View.INVISIBLE);
                break;
        }
    }

    public void startNewOrder(){
        getItemsList();
    }

    /******Listeners********/

    private class NewOrderButtonListener implements View.OnClickListener {

        @Override
        public void onClick(View view) {
            if(adapterAddedItem.getCount() != 0) { //if there are items added ask if hte user is sure in starts a new order
                AlertDialog.Builder builder = new AlertDialog.Builder(activity);

                builder.setMessage(R.string.add_items_confirm_new_order);
                builder.setPositiveButton(R.string.dialog_yes, new DialogInterface.OnClickListener() {

                    @Override
                    public void onClick(DialogInterface dialog, int which) {
                        getItemsList();
                    }
                });
                builder.setNegativeButton(R.string.dialog_back, null);
                builder.create().show();
            } else {
                addedItemsListInterface.newOrderButtonClick();
                startNewOrder();
            }
        }
    }

    private class EndingOrderButtonListener implements View.OnClickListener {
        @Override
        public void onClick(View view) {

            ArrayList<AddedItem> itemsAdded = adapterAddedItem.getObjects();
            addedItemsListInterface.finalizeAddingItems(itemsAdded, codPriceTable);

        }
    }

    private class ItemListClickListener implements AdapterView.OnItemClickListener{

        @Override
        public void onItemClick(AdapterView<?> adapterView, View view, int i, long l) {

            Item item = (Item)adapterView.getItemAtPosition(i);

            if(searchItem != null)searchItem.setQuery("", false);

            if(adapterItems.getCount() >= i) {
                setSelectedItem(item);
                refreshItemsCfgScreen();
            }
        }
    }

    private class checkBoxStockItemListener implements View.OnClickListener {

        @Override
        public void onClick(View view) {

            if(selectedItem != null){
                refreshItemsCfgScreen();
            }

        }
    }
    private class QueryItemCfgListener implements SearchView.OnQueryTextListener, SearchView.OnCloseListener {
        @Override
        public boolean onQueryTextSubmit(String s) {
            queryItemsCfgText = s;
            showResults(s);
            return false;
        }

        @Override
        public boolean onQueryTextChange(String s) {
            showResults(s);
            return false;
        }

        private void showResults(String query) {
            if(adapterItemsCfg != null) {
                adapterItemsCfg.getFilter().filter(query);
            }
        }

        @Override
        public boolean onClose() {
            showResults("");
            return false;
        }
    }

    private class QueryItemListener implements SearchView.OnQueryTextListener, SearchView.OnCloseListener {
        @Override
        public boolean onQueryTextChange(String newText) {

            queryItemsText = newText;
            showResults(newText);
            return false;
        }

        @Override
        public boolean onQueryTextSubmit(String query) {
            showResults(query);
            return false;
        }

        private void showResults(String query) {
            if(adapterItems != null) adapterItems.getFilter().filter(query);
        }

        @Override
        public boolean onClose() {
            showResults("");
            return false;
        }
    }

    private class ItemCfgClickListener implements AdapterView.OnItemClickListener {

        @Override
        public void onItemClick(AdapterView<?> adapterView, View view, int i, long l) {
            ItemCfg itemCfg = (ItemCfg)adapterView.getItemAtPosition(i);
            itemsManager.requestItemCfgPrice(codSelectedCompany, itemCfg.getvItcomid(), codPriceTable, itemCfg.getCodItem(), order.getClientId(), order.getEstablishmentId());
            dialogAddItem.showAddItem(order.getCompanyId(), itemCfg);
        }
    }

    @Override
    public void addItem(AddedItem addedItem) {
        if(searchItemCfg != null)searchItemCfg.setQuery("", false);
        searchItem.requestFocus();
        orderManager.addItemToOrder(order, addedItem);
    }

    @Override
    public void saveItem(AddedItem oldNew, AddedItem newItem) {
        adapterAddedItem.remove(oldNew);
        newItem.setId(oldNew.getId());
        newItem.setTpmnt(oldNew.getTpmnt());
        orderManager.addItemToOrder(order, newItem);
    }

    @Override
    public void removeItem(AddedItem removedItem) {
        if(removedItem.getTpmnt().equals("A")){
            orderManager.removeItemFromOrder(removedItem.getId());
        }
        adapterAddedItem.remove(removedItem);
        adapterAddedItem.notifyDataSetChanged();
    }

    /***********************/

    private void getItemsList(){
            itemsManager.requestItems(codSelectedCompany);
    }

    /*****Webservice********/

    @Override
    public void failOnItemsRetrieve() {
        ShowMessage.alertDialog2(activity, R.string.stockfragment_failonretrieveitems,
                new DialogInterface.OnClickListener() {

                    @Override
                    public void onClick(DialogInterface dialog, int which) {
                        switch (which) {
                            case DialogInterface.BUTTON_NEGATIVE:
                                activity.finish();
                                break;
                            case DialogInterface.BUTTON_POSITIVE:
                                itemsManager.requestItems(codSelectedCompany);
                                break;
                        }
                    }
                });
    }

    @Override
    public void onItemsRetrieve(ArrayList<Item> items) {
        initItemList(items);
    }

    @Override
    public void failOnItemsCfgRetrieve() {
        ShowMessage.alertDialog2(activity, R.string.stockfragment_failonretrieveitemscfg,
                new DialogInterface.OnClickListener() {

                    @Override
                    public void onClick(DialogInterface dialog, int which) {
                        switch(which) {
                            case DialogInterface.BUTTON_NEGATIVE:
                                break;
                            case DialogInterface.BUTTON_POSITIVE:
                                if(selectedItem != null) {
                                    refreshItemsCfgScreen();
                                }
                                break;
                        }
                    }
                });
    }

    @Override
    public void onItemsCfgRetrieve(ArrayList<ItemCfg> items) {
        Item item = getSelectedItem();
        TextView itemName = (TextView)addItemsView.findViewById(R.id.item_selected);
        itemName.setText(item.getName());

        adapterItemsCfg.clear();
        adapterItemsCfg.addAll(items);
        adapterItemsCfg.notifyDataSetChanged();
    }

    @Override
    public void failOnRetrieveItemCfgPrice() {

    }

    @Override
    public void onItemCfgPriceRetrieve(double value) {
        dialogAddItem.setItemPrice(value);
    }



    /***********************/

    /*****Geters and Setters****/
    public void setmServerDataCacheBinder(ServerDataCacheService mServerDataCacheBinder) {
        itemsManager.setmServerDataCacheBinder(mServerDataCacheBinder);
    }

    public void setCodSelectedCompany(int codSelectedCompany) {
        if(codSelectedCompany != this.codSelectedCompany){
            this.codSelectedCompany = codSelectedCompany;
            setAddItemsMode(AddItemsScreen.Mode.WAIT_NEW_ORDER);
        }
    }

    public void setNewOrder(Order order) {
        this.order = order;

    }

    public void setAddItemsView(LinearLayout addItemsView) {
        this.addItemsView = addItemsView;
    }

    public void setSelectedItem(Item selectedItem) {
        this.selectedItem = selectedItem;
    }

    public Item getSelectedItem() {
        return selectedItem;
    }

    public void setPriceTableList(ArrayList<PriceTable> priceTableArrayList) {
        adapterPriceTable.clear();
        adapterPriceTable.addAll(priceTableArrayList);
    }
    public void selectPriceTable(String priceTableId){
        PriceTable priceTable = (PriceTable)findOrderParamById(adapterPriceTable, priceTableId);
        if(priceTable == null) return;
        codPriceTable = priceTable.getId();
        Spinner priceTableSpinner = (Spinner)addItemsView.findViewById(R.id.price_table_spinner);
        if(priceTableSpinner != null) {
            int position = adapterPriceTable.getPosition(priceTable);
            priceTableSpinner.setSelection(position);
        }
    }

    public void setEstablishmentName(String establishmentName){
        this.establishmentName = establishmentName;
        TextView clientNameView = (TextView)addItemsView.findViewById(R.id.order_establishment);
        clientNameView.setText(establishmentName);
    }

    public class SelectPriceTableListener implements AdapterView.OnItemSelectedListener {

        public void onItemSelected(AdapterView<?> parent,
                                   View view, int pos, long id) {
            PriceTable priceTable = (PriceTable)parent.getItemAtPosition(pos);
            codPriceTable = priceTable.getId();
        }

        public void onNothingSelected(AdapterView parent) {
            // Do nothing.
        }
    }

    private OrderParam findOrderParamById(ArrayAdapter<?> adapter, String id){
        OrderParam ret = null;
        OrderParam aux;
        if(adapter != null) {
            for(int i = 0;i < adapter.getCount(); i++){
                aux =  (OrderParam)adapter.getItem(i);
                if(aux.getId().equals(id)){
                    ret = aux;
                    break;
                }
            }
        }
        return ret;
    }

    private class LevaLoteClickListener implements CompoundButton.OnCheckedChangeListener {

        @Override
        public void onCheckedChanged(CompoundButton compoundButton, boolean b) {
            levaLoteParaPedido = b;
        }
    }

    @Override
    public void orderInitialized(Order order) {
    }

    @Override
    public void orderFinalized(Order order) {
    }

    @Override
    public void orderFromSaveToFinalized(String orderId) {
    }

    @Override
    public void onValorBrutoReturn(String valorBruto) {
    }

    @Override
    public void onValorLiquidoReturn(String valorLiquido) {
    }

    @Override
    public void onItemsAdded(ArrayList<AddedItem> itemsSent) {
    }

    @Override
    public void onItemRemoved(String itemId) {
        refreshItemsCfgScreen();
    }

    @Override
    public void onItemAdded(AddedItem item) {
        refreshItemsCfgScreen();
        adapterAddedItem.add(item);
        adapterAddedItem.notifyDataSetChanged();
    }

    @Override
    public void orderRemoved(String resultString) {
    }

    private void refreshItemsCfgScreen(){
        boolean inStock = stockCheckBox.isChecked();
        if(selectedItem != null) {
            itemsManager.requestItemsCfg(selectedItem.getCodItem(), codSelectedCompany, inStock, codPriceTable);
        }
    }
}
